package com.ad.aidai.fragments.select_school;

import android.content.Context;
import android.view.View;

import com.ad.aidai.bean.ItemSchool;
import com.ad.aidai.bean.School;
import com.ad.aidai.common.RxBus;
import com.ad.aidai.common.listener.RecyclerViewListener;
import com.ad.aidai.common.utils.CheckUtil;
import com.ad.aidai.common.utils.PinyinUtils;
import com.ad.aidai.events.CommonEvent;
import com.ad.aidai.network.NetWork;
import com.ad.aidai.network.StatusCodeFromNet;
import com.ad.aidai.network.result.GetSchoolFromNet;
import com.orhanobut.logger.Logger;
import com.umeng.analytics.MobclickAgent;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import rx.Observable;
import rx.Observer;
import rx.Subscriber;
import rx.android.schedulers.AndroidSchedulers;
import rx.schedulers.Schedulers;
import rx.subscriptions.CompositeSubscription;


/**
 * SelectSchoolPresenter
 * <p>
 * Created by Yusoxn on 2017/1/23.
 */

public class SelectSchoolPresenter implements SelectSchoolContract.Presenter {

    class CMP implements Comparator<ItemSchool> {

        @Override
        public int compare(ItemSchool o1, ItemSchool o2) {
            School firstSchool = (School) o1.getItemMessage();
            School secondSchool = (School) o2.getItemMessage();

            int firstSchoolChar0 = (PinyinUtils.getFirstSpell(firstSchool.getSchoolName()).toUpperCase().charAt(0) +
                    "").hashCode();
            int secondSchoolChar0 = (PinyinUtils.getFirstSpell(secondSchool.getSchoolName()).toUpperCase().charAt(0)
                    + "").hashCode();

            boolean isPinyinFirst = (firstSchoolChar0 >= "A".hashCode() && firstSchoolChar0 <= "Z".hashCode());
            boolean isPinyinSecond = (secondSchoolChar0 >= "A".hashCode() && secondSchoolChar0 <= "Z".hashCode());

            if (isPinyinFirst && !isPinyinSecond) {
                return 1;
            } else if (!isPinyinFirst && isPinyinSecond) {
                return -1;
            }

            String firstSchoolName_Pinyin = PinyinUtils.getPingYin(firstSchool.getSchoolName());
            String secondSchoolNamePinyin = PinyinUtils.getPingYin(secondSchool.getSchoolName());

            return firstSchoolName_Pinyin.compareTo(secondSchoolNamePinyin);
        }
    }

    private Context mContext;
    private SelectSchoolContract.View mView;
    private CompositeSubscription mSubscriptions;

    private SelectSchoolAdapter mAdapter;
    private int nearLength = 0;
    private Map<String, Integer> charMap = new HashMap<>();
    /**
     * 保存所有学校信息
     */
    private List<ItemSchool> allSchools;
    /**
     * 要展示出来的学校信息
     */
    private List<ItemSchool> showSchools;
    /**
     * 搜索出来的学校信息
     */
    private List<ItemSchool> searchSchools;
    /**
     * 定位出来的附近的学校信息
     */
    private List<ItemSchool> nearbySchools;

    private List<School> schoolsAll;

    private List<School> schoolsNearby;

    public SelectSchoolPresenter(Context context, SelectSchoolContract.View view) {
        this.mContext = context;
        this.mView = view;
        mSubscriptions = new CompositeSubscription();
        mView.setPresenter(this);
        initData();
    }

    @Override
    public void subscribe() {

    }

    @Override
    public void unSubscribe() {
        mContext = null;
        mView = null;
        mSubscriptions.clear();
    }

    private void initData() {

        allSchools = new ArrayList<>();
        showSchools = new ArrayList<>();
        searchSchools = new ArrayList<>();
        nearbySchools = new ArrayList<>();
        schoolsAll = new ArrayList<>();
        schoolsNearby = new ArrayList<>();

        mAdapter = new SelectSchoolAdapter(mContext, showSchools);
        mAdapter.setOnItemClickListener(new RecyclerViewListener.OnRecyclerViewItemClickListener() {
            @Override
            public void onItemClick(View view, int position) {
                School school = (School) showSchools.get(position).getItemMessage();
                RxBus.getInstance().postEvent(new CommonEvent<>(CommonEvent.SELECT_SCHOOL_BIND, school));
                mView.itemClickExit();
            }
        });
    }

    private void initSchools() {

        for (School school : schoolsAll) {
            allSchools.add(new ItemSchool<>(ItemSchool.ITEM_DATA, new School(school.getSchoolId(), school
                    .getSchoolName())));
        }
        Collections.sort(allSchools, new CMP());

        int nowChar = -1;
        int len = allSchools.size();
        for (int i = 0; i < len; ++i) {
            School school = (School) allSchools.get(i).getItemMessage();
            String str0 = PinyinUtils.getFirstSpell(school.getSchoolName()).toUpperCase().charAt(0) + "";
            if (nowChar != str0.hashCode()) {
                nowChar = str0.hashCode();
                if (!(nowChar >= "A".hashCode() && nowChar <= "Z".hashCode())) {
                    str0 = "#";
                }
                allSchools.add(i + nearLength, new ItemSchool<>(ItemSchool.ITEM_CHARACTER, str0));
                charMap.put(str0, i);
                if (str0.equals("#")) {
                    break;
                }
                len++;
                i++;
            }
        }

        for (School school : schoolsNearby) {
            if (searchInAllSchool(school)) {
                nearbySchools.add(new ItemSchool<>(ItemSchool.ITEM_DATA, new School(school.getSchoolId(), school.getSchoolName())));
            }
        }
        if (nearbySchools.size() > 0) {
            nearbySchools.add(0, new ItemSchool<>(ItemSchool.ITEM_CHARACTER, "附近学校"));
        }
        nearLength = nearbySchools.size() + 1;

        showSchools.addAll(nearbySchools);
        showSchools.addAll(allSchools);

        mAdapter.notifyDataSetChanged();
    }

    @Override
    public SelectSchoolAdapter getAdapter() {
        return mAdapter;
    }

    private boolean searchInAllSchool(School school) {
        if(school == null) {
            return false;
        }
        for(School s : schoolsAll) {
            if(s.getSchoolId().equals(school.getSchoolId())) {
                return true;
            }
        }
        return false;
    }

    @Override
    public void loadSchool() {
        NetWork.getAccountOperationApi()
                .getSchool()
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(new Observer<GetSchoolFromNet>() {
                    @Override
                    public void onCompleted() {

                    }

                    @Override
                    public void onError(Throwable e) {
                        MobclickAgent.reportError(mContext, e);
                        Logger.t("school").e(e.getMessage());
                    }

                    @Override
                    public void onNext(GetSchoolFromNet getSchoolFromNet) {
                        Logger.t("school").i(getSchoolFromNet.toString());
                        if (getSchoolFromNet.getCode() == StatusCodeFromNet.CODE_SUCCESS) {
                            schoolsAll = getSchoolFromNet.getData();
                            initSchools();
                        } else {

                        }
                    }
                });

    }

    @Override
    public int getSelectItemPosition(int index, String text) {
        if (index == 0) {
            return 0;
        } else if (charMap.containsKey(text)) {
            return charMap.get(text) + nearLength;
        }
        return -1;
    }

    @Override
    public void searchSchool(final String inputStr) {
        Observable
                .create(new Observable.OnSubscribe<Object>() {
                    @Override
                    public void call(Subscriber<? super Object> subscriber) {
                        if (CheckUtil.checkStrNull(inputStr)) {
                            searchSchools.clear();
                            showSchools.clear();
                            showSchools.addAll(nearbySchools);
                            showSchools.addAll(allSchools);
                        } else {
                            searchSchools.clear();
                            StringBuilder matchStr = new StringBuilder();
                            matchStr.append("(.*)");
                            for (int i = 0; i < inputStr.length(); ++i) {
                                matchStr.append(inputStr.charAt(i)).append("(.*)");
                            }
                            for (int i = 0; i < allSchools.size(); ++i) {
                                if (allSchools.get(i).getItemType() == ItemSchool.ITEM_DATA) {
                                    School school = (School) allSchools.get(i).getItemMessage();
                                    if (school.getSchoolName().matches(matchStr.toString())) {
                                        searchSchools.add(new ItemSchool<>(ItemSchool.ITEM_DATA, school, inputStr));
                                    }
                                }
                            }
                            showSchools.clear();
                            if (searchSchools.size() > 0) {
                                showSchools.addAll(searchSchools);
                            } else {
                                showSchools.add(new ItemSchool<>(ItemSchool.ITEM_EMPTY, null));
                            }
                        }
                        subscriber.onCompleted();
                    }
                })
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(new Subscriber<Object>() {
                    @Override
                    public void onCompleted() {
                        mAdapter.notifyDataSetChanged();
                    }

                    @Override
                    public void onError(Throwable e) {
                        MobclickAgent.reportError(mContext, e);
                        Logger.t(this.getClass().getSimpleName()).e(e.getMessage());
                    }

                    @Override
                    public void onNext(Object o) {
                    }
                });
    }
}
